#include<iostream>
#include<mutex>
#include<condition_variable>
#include<queue>
using namespace std;


template <class T>
class safequeue{
private:

queue<T> _st;
mutex _mutex;
condition_variable _canpush;
condition_variable _canpop;
int max_size;

public:
safequeue(int num=0)
	:max_size(num)
{

}


int size() const
{
	unique_lock<mutex>lock(_mutex);
	return _st.size();

}
bool Empty() const
{

	unique_lock<mutex>lock(_mutex);
	return _st.empty();


}

void enqueue(const T&x)
{
	unique_lock<mutex>lock(_mutex);
	if (max_size > 0 && max_size == _st.size())
	{
		_canpush.wait(lock);
	}
	_st.push(x);
	
	
      _canpop.notify_one();
	

}
T dequeue()
{
	unique_lock<mutex>lock(_mutex);
	_canpop.wait(lock, [this] {return !_st.empty(); });
	T ret = _st.front();
	_st.pop();
	if (max_size > 0)
		_canpush.notify_one();

}

};

int main()
{

	safequeue<int>cc(6);
	cc.enqueue(1);
	cc.enqueue(2);
	cc.enqueue(3);
	cc.enqueue(4);
	cc.enqueue(5);



}